#ifndef frm_control_TPageControl_H
#define frm_control_TPageControl_H

#include "frm_control_TButton.h"
#include "frm_control_TString.h"

namespace frm { namespace control {

///////////////////////////////////////////////////////////////////////////////
struct TPageButton;
struct TPage;
struct TPageControl;
///////////////////////////////////////////////////////////////////////////////

struct TPageControlClient : public TPanel
{
  struct TStyle : public TPanel::TStyle
  {
    svl_Type(TPanel::TStyle)
  };
  //
  TPageControl *PageControl;
  //
  TPageControlClient(TPageControl *PageControl);
 ~TPageControlClient();
  //
  virtual void AddChildFirst (TComponent *Add,bool EnDelete = true);
  virtual void AddChildLast  (TComponent *Add,bool EnDelete = true);
  virtual void AddChildBefore(TComponent *Add,TComponent *Curr,bool EnDelete = true);
  virtual void AddChildAfter (TComponent *Add,TComponent *Curr,bool EnDelete = true);
  //
  virtual void DeleteChild(int N);
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TPanel::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
  
private:
  svl_Except;
};

///////////////////////////////////////////////////////////////////////////////

struct TPageControlButtons : public TPanel
{
  struct TStyle : public TPanel::TStyle
  {
    svl_Type(TPanel::TStyle)
  };
  //
  TPageControl *PageControl;
  //
  TPageControlButtons(TPageControl *PageControl);
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TPanel::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
};

/*//////////////////////////////////////////////////////////////////////////////
struct TPageString : public TString
{
  struct TStyle : public TString::TStyle
  {
    svl_Type(TString::TStyle)
  };
  //
  TPageString(TPageButton *Parent);
  //
  virtual bool TComponent_FocusEnable() { return false;}
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TString::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
};
*/

///////////////////////////////////////////////////////////////////////////////

struct TPageButton : public TButton
{
  struct TStyle : public TButton::TStyle
  {
    svl_Type(TButton::TStyle)
  };
  //
  TPage       *Page; 
  //TPageString *String;
  //
  TPageButton(TPage *Page);
  //
  virtual void UpdateDown(bool V);
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TButton::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
};

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////

struct TPage : public TPanel
{
  struct TStyle : public TPanel::TStyle
  {
	//TPageButton::TStyle Button;
	svl_Type(TPanel::TStyle)
	//
	//
    virtual void SetFromParent(frm::TStyle *Parent);
    virtual svl::TInfoParam AddInfoTo(svl::TInfoParam Info);
  };
  //
  TPageControl *PageControl; 
  TPageButton  *Button;
  //
  TPage(TWindow &Window);
 ~TPage(); 
  //
  virtual void UpdateVisible(bool V);
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TPanel::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
};

///////////////////////////////////////////////////////////////////////////////

struct TPageControl : public TPanel
{
  struct TStyle : public TPanel::TStyle
  {
	TPageControlButtons::TStyle Buttons;
	TPageControlClient ::TStyle Client;
    
	void operator=(const TStyle &From){
		Buttons = From.Buttons;
		Client  = From.Client;
	}
	//
    virtual void SetFromParent(frm::TStyle *Parent);
    virtual svl::TInfoParam AddInfoTo(svl::TInfoParam Info);
	//
	svl_Type(TPanel::TStyle)
  };
  ////////////////////////////////////////////////////////
  struct TEventsList; struct TEvents : public svl::TEvents
  {
    ///////////////////////////////////////////
    struct TParam : public svl::TEvents::TParam
    {
      TPageControl &Sender;
      //
      TParam(TEventsList &eventsList) : svl::TEvents::TParam(eventsList),Sender(eventsList.Sender) {}
    };
    ////////////////////////////////
    struct TShowPage : public TParam
    {
      TPage *Page;
      // Before:
      bool &EnShow;
      //
      TShowPage(TEventsList &eventsList,TPage *page,bool &enShow) : TParam(eventsList),Page(page),EnShow(enShow) {}
    };
    virtual void TEvents_BeforeShowPage(TShowPage &Param) { TEvents *P = (TEvents*)Param.GetPrev(); if (P) { P->TEvents_BeforeShowPage(Param);} }
    virtual void TEvents_AfterShowPage (TShowPage &Param) { TEvents *P = (TEvents*)Param.GetPrev(); if (P) { P->TEvents_AfterShowPage (Param);} }
  };
  ////////////////////////////////////////////
  struct TEventsList : public svl::TEventsList
  {
    TPageControl &Sender;
    //
    TEventsList(TPageControl &sender) : Sender(sender),svl::TEventsList(Default()) {}
    //
    void Link  (TEvents &V) { svl::TEventsList::Link  (V);}
    void Unlink(TEvents &V) { svl::TEventsList::Unlink(V);}

  private:
    static TEvents &Default() { static TEvents E; return E;}
    TEvents &Get() { return (TEvents&)svl::TEventsList::GetBot();}
    friend TPage;
  }
  Events;
  //
  enum EButtons { EButtons_Left,EButtons_Right,EButtons_Top,EButtons_Bottom };
  //
  TPageControlButtons *Buttons;
  TPageControlClient  *Client;
  //
  TPageControl(TWindow &Window);
 ~TPageControl();
  //
  void SetStyle(TStyle &V);
  //
  void SetEButtons(EButtons V = EButtons_Top);
  //
  TPage *GetVisiblePage() { return visiblePage; }
  //
  void TComponent_InheritStyleFrom(TTableOfStyles &ParentStyles)
  { 
    TStyle *Style = dynamic_cast<TStyle*>(ParentStyles.SearchByEqualType(TStyle::TType())); if (Style) {
      SetStyle(*Style);
    } 
    else {
      //TPanel::TComponent_InheritStyleFrom(ParentStyles);
    }
  }
  
private:
  TPage *visiblePage;
  friend TPage;
};

///////////////////////////////////////////////////////////////////////////////
}}

#endif
